package com.aismy.admin.service.impl;

import com.aismy.admin.dto.LoginDTO;
import com.aismy.admin.dto.RegisterDTO;
import com.aismy.admin.dto.UpdateUserDto;
import com.aismy.admin.entity.SysUser;
import com.aismy.admin.mapper.SysUserMapper;
import com.aismy.admin.service.UserService;
import com.aismy.admin.utils.JwtUtils;
import com.aismy.admin.utils.PasswordUtils;
import com.aismy.admin.vo.LoginVO;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import lombok.RequiredArgsConstructor;
import org.springframework.stereotype.Service;
import org.springframework.util.StringUtils;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.aismy.admin.dto.UserDTO;

@Service
@RequiredArgsConstructor
public class UserServiceImpl extends ServiceImpl<SysUserMapper, SysUser> implements UserService {

    private final JwtUtils jwtUtils;
    private final PasswordUtils passwordUtils;

    @Override
    public LoginVO login(LoginDTO loginDTO) {
        // 查询用户
        SysUser user = this.getOne(
                new LambdaQueryWrapper<SysUser>()
                        .eq(SysUser::getUsername, loginDTO.getUsername())
        );
        if (user == null || !passwordUtils.verify(loginDTO.getPassword(), user.getPassword())) {
            throw new RuntimeException("用户名或密码错误");
        }

        if (user.getStatus() == 0) {
            throw new RuntimeException("账号已被禁用");
        }
        // 生成token
        String token = jwtUtils.generateToken(user);
        // 构建返回对象
        LoginVO loginVO = new LoginVO();
        loginVO.setToken(token);

        // 清除敏感信息
        user.setPassword(null);
        loginVO.setUserInfo(user);
        return loginVO;
    }

    @Override
    public void register(RegisterDTO registerDTO) {
        // 检查用户名是否已存在
        if (this.count(new LambdaQueryWrapper<SysUser>()
                .eq(SysUser::getUsername, registerDTO.getUsername())) > 0) {
            throw new RuntimeException("用户名已存在");
        }
        // 创建新用户
        SysUser user = new SysUser();
        user.setUsername(registerDTO.getUsername());
        user.setPassword(passwordUtils.encrypt(registerDTO.getPassword()));
        user.setRole(registerDTO.getRole());
        // 保存用户
        this.save(user);
    }

    @Override
    public Page<SysUser> getUserPage(Integer page, Integer size, String query) {
        Page<SysUser> pageParam = new Page<>(page, size);
        LambdaQueryWrapper<SysUser> wrapper = new LambdaQueryWrapper<SysUser>()
                .like(StringUtils.hasText(query), SysUser::getUsername, query)
                .orderByDesc(SysUser::getCreatedAt);
        return this.page(pageParam, wrapper);
    }

    @Override
    public void addUser(UserDTO userDTO) {
        // 检查用户名是否已存在
        if (this.count(new LambdaQueryWrapper<SysUser>()
                .eq(SysUser::getUsername, userDTO.getUsername())) > 0) {
            throw new RuntimeException("用户名已存在");
        }

        SysUser user = new SysUser();
        user.setUsername(userDTO.getUsername());
        user.setPassword(passwordUtils.encrypt(userDTO.getPassword()));
        user.setRole(userDTO.getRole());
        user.setStatus(userDTO.getStatus());
        user.setIsConsultant(userDTO.getIsConsultant());
        user.setSpecialty(userDTO.getSpecialty());
        user.setIntroduction(userDTO.getIntroduction());

        this.save(user);
    }

    @Override
    public void updateUser(UserDTO userDTO) {
        SysUser user = this.getById(userDTO.getId());
        if (user == null) {
            throw new RuntimeException("用户不存在");
        }

        // 检查用户名是否被其他用户使用
        if (!user.getUsername().equals(userDTO.getUsername()) &&
                this.count(new LambdaQueryWrapper<SysUser>()
                        .eq(SysUser::getUsername, userDTO.getUsername())) > 0) {
            throw new RuntimeException("用户名已存在");
        }

        user.setUsername(userDTO.getUsername());
        if (StringUtils.hasText(userDTO.getPassword())) {
            user.setPassword(passwordUtils.encrypt(userDTO.getPassword()));
        }
        user.setRole(userDTO.getRole());
        user.setStatus(userDTO.getStatus());
        user.setIsConsultant(userDTO.getIsConsultant());
        user.setSpecialty(userDTO.getSpecialty());
        user.setIntroduction(userDTO.getIntroduction());

        this.updateById(user);
    }

    @Override
    public void updateStatus(Long id, Integer status) {
        SysUser user = new SysUser();
        user.setId(id);
        user.setStatus(status);
        this.updateById(user);
    }

    // 新增：获取专家列表
    public Page<SysUser> getExpertPage(Integer page, Integer size, String query) {
        Page<SysUser> pageParam = new Page<>(page, size);
        LambdaQueryWrapper<SysUser> wrapper = new LambdaQueryWrapper<SysUser>()
                .eq(SysUser::getIsConsultant, 1)
                .like(StringUtils.hasText(query), SysUser::getUsername, query)
                .orderByDesc(SysUser::getCreatedAt);
        return this.page(pageParam, wrapper);
    }

    @Override
    public Page<SysUser> getConsultantPage(Integer page, Integer size, String query) {
        LambdaQueryWrapper<SysUser> wrapper = new LambdaQueryWrapper<>();
        wrapper.eq(SysUser::getRole, "EXPERT")
                .eq(SysUser::getIsConsultant, 1)
                .eq(SysUser::getStatus, 1)  // 确保用户状态为启用
                .and(!StringUtils.isEmpty(query), w -> w
                        .like(SysUser::getUsername, query)
                        .or()
                        .like(SysUser::getSpecialty, query)
                )
                .orderByDesc(SysUser::getCreatedAt);

        return this.page(new Page<>(page, size), wrapper);
    }

    @Override
    public void updateUserProfile(UpdateUserDto userDTO) {
        SysUser user = this.getById(userDTO.getId());
        if (user == null) {
            throw new RuntimeException("用户不存在");
        }
        if (StringUtils.hasText(userDTO.getAvatar())) {
            user.setAvatar(userDTO.getAvatar());
        }
        if (StringUtils.hasText(userDTO.getRealName())) {
            user.setRealName(userDTO.getRealName());
        }
        if (StringUtils.hasText(userDTO.getPassword())) {
            user.setPassword(passwordUtils.encrypt(userDTO.getPassword()));
        }
        this.updateById(user);
    }
} 